package xjf;
//本类用来模式实现LinkedList
public class MyLinkedList<E> {

    private class Node{
        E element;
        Node previous;
        Node next;

        public Node(E element) {
            this.element=element;
        }
    }
    private Node first;
    private Node last;
    private int count;

    //像集合中添加元素
    public void add(E element){
        Node node=new Node(element);
        if(count==0){
            this.first=node;
        }else{
            this.last.next=node;
            node.previous=this.last;
      }
        this.last=node;
        count++;
    }
    //指定下标添加元素
    public void add(int index,E element){
        Node node=new Node(element);
        if(index==0){
            this.first.previous=node;
            node.next=this.first;
            this.first=node;
        }else if(index==count){
            this.last.next=node;
            node.previous=this.last;
            this.last=node;
        }else {
            Node target=getNode(index);
            node.next=target;
            node.previous=target.previous;
            target.previous.next=node;
            target.previous=node;
        }
        count++;
    }
    //根据下标获取结点
    private Node getNode(int index){
        if(index<0||index>=count){
            throw new IndexOutOfBoundsException("下标越界");
        }
        Node node=this.first;
        for (int i = 0; i <index; i++) {
            node=node.next;
        }
        return node;
    }
    //删除指定下标的元素
    public E remove(int index){
        Node node=getNode(index);
        removeNode(node);
        return node.element;
    }
    //删除节点
    private void removeNode(Node node){
        if(count==1){
            this.first=null;
            this.last=null;
            count--;
            return;
        }
        if (node==this.first){
            this.first=this.first.next;
            this.first.previous.next=null;
            this.first.previous=null;
        }else if(node==this.last){
            this.last=this.last.previous;
            this.last.next.previous=null;
            this.last.next=null;
        }else {
            node.previous.next=node.next;
            node.next.previous=node.previous;
            node.next=null;
            node.previous=null;
        }
        count--;
    }

    // 根据元素进行删除
    public boolean remove(E element){
        Node node=getNode(element);
        if (node==null){
            return false;
        }else {
            removeNode(node);
            return true;
        }
    }
    private Node getNode(E element){
        Node node=this.first;
        while (node!=null){
            if(node.element.equals(element)){
                return node;
            }
            node=node.next;
        }
        return null;
    }
    //清空链表
    public void clear(){
        this.first=null;
        this.last=null;
        count=0;
    }
    //修改指定下标节点中的元素值
    public E set(int index,E element){
        Node node=getNode(index);
        E ele=node.element;
        node.element=element;
        return ele;
    }
    //根据下标获取指定的元素
    public E get(int index){
        Node node=getNode(index);
        return node.element;
    }
    //得到链表中节点的个数
    public int size(){
        return count;
    }
    //是否包含这个元素
    public boolean contains(E element){
        return indexOF(element)!=-1;
    }
    //得到元素第一次出现的下标
    public int indexOF(E element){
        Node node=this.first;
        for (int i = 0; i < count; i++) {
            if (node.element.equals(element)){
                return i;
            }
        }
        return -1;
    }
    //toString
    public String toString(){
        if (count==0)
            return "[]";
        StringBuilder stringBuilder=new StringBuilder("[");
        Node node=this.first;
        for (int i = 0; i < count; i++) {
            stringBuilder.append(node.element).append(",");
            node= node.next;
        }
        stringBuilder.replace(stringBuilder.length()-1,stringBuilder.length(),"]");
        return stringBuilder.toString();

    }
}
